/*
 *  本demo程序实现了如下功能：
 * 1. 程序参数解析
 * 2. 程序help和usage实现方法
 * 3. 输出日志到/var/log/auth.log的实现方法
 * 将l0030-0/l0031-0放到/data目录下，执行以下命令可使a9999-0寻找到/data目录下的库
 * export LD_LIBRARY_PATH=/data/
 * ./a9999-0 -b -t 10 -n 2
*/
#include "t0022-0.h"
#include "dxtviewer.h"

#define MODNAME		"[T22M]"

void usage(void)
{
	printf("Usage: t0022-0 [OPTION]\n");
	printf("  -v	print version\n");
	printf("  -h	print this help\n");
	exit(0);
}

void t0022_0_version(char *image)
{
	printf("%s %s Build: %s %s\n", image, T0022_0_VERSION, __DATE__, __TIME__);
	exit(0);
}

int shm_read() {
    int retval = -1;
	int8_t val;
	__maybe_unused entry_handle hentry;
	__maybe_unused struct l0032_xtable xtable;

	printf("#### READ SHARED MEMORY ####\n");
    // open dataxchgtable.
	if(l0032_xtable_open(NULL, 0) == NULL) {
		ERRSYS_FATALPRINT("Fail to open Data Exchange Table\n");
		goto err1;
	}
	// parse dxt conf.
	if(l0032_xtable_load_conf(&xtable, A9999_0_DXT_CONFFILE) != 0) {
		ERRSYS_FATALPRINT("xtable load failed, iniconf:%s\n", A9999_0_DXT_CONFFILE);
		goto err2;
	}
	// dump xtable.
	printf("---- DUMP INICONF ----\n");
	l0032_xtable_dump_conf(&xtable);
	printf("\n\n");

	printf("---- DUMP DXTINFO ----\n");
	l0032_xtable_dump(&xtable);
	printf("\n\n");

	hentry = l0032_get_entry("data");

	l0032_xtable_read(hentry, 0, &val, sizeof(val));
	printf("read val 0x%x\n", val);

    retval = 0;
err2:
    l0032_xtable_close();
err1:
    return retval;
}

int shm_load(){
    int retval = -1;
	struct l0032_xtable xtable;
	
	printf("#### LOAD CONFIG %s ####\n", A0013_0_DXT_CONFFILE);
    // open dataxchgtable.
	if(l0032_xtable_open(NULL, 0) == NULL) {
		ERRSYS_FATALPRINT("Fail to open Data Exchange Table\n");
		goto err1;
	}
	// parse dxt conf.
	if(l0032_xtable_load_conf(&xtable, A0013_0_DXT_CONFFILE) != 0) {
		ERRSYS_FATALPRINT("xtable load failed, iniconf:%s\n", A0013_0_DXT_CONFFILE);
		goto err2;
	}
err2:
    l0032_xtable_close();
err1:
	printf("%s quit\n", __func__);
    return retval;
}

int shm_write(int v) {
    int retval = -1;
	int val;
	entry_handle hentry;
	struct l0032_xtable xtable;
	
	printf("#### WRITE SHARED MEMORY ####\n");
    // open dataxchgtable.
	if(l0032_xtable_open(NULL, 0) == NULL) {
		ERRSYS_FATALPRINT("Fail to open Data Exchange Table\n");
		goto err1;
	}
	// parse dxt conf.
	if(l0032_xtable_load_conf(&xtable, A9999_0_DXT_CONFFILE) != 0) {
		ERRSYS_FATALPRINT("xtable load failed, iniconf:%s\n", A9999_0_DXT_CONFFILE);
		goto err2;
	}
	hentry = l0032_get_entry("data");

	val = -1;
	l0032_xtable_read(hentry, 0, &val, sizeof(val));
	printf("1st read val %x\n", val);

	val = v;
	retval = l0032_xtable_write(hentry, 0, &val);
	if (retval != sizeof(int8_t)) {
		printf("write error retval %d\n", retval);
	}
	else {
		printf("write val %d\n", val);
	}
	val = -1;
	l0032_xtable_read(hentry, 0, &val, sizeof(val));
	printf("2nd read val %x\n", val);

    retval = 0;
err2:
    l0032_xtable_close();
err1:
	printf("%s quit\n", __func__);
    return retval;
}

int sharedmemory_open() {
    int retval = -1;
    // open dataxchgtable.
	printf("#### OPEN SHARED MEMORY ####\n");
	if(l0032_xtable_open(NULL, 1) == NULL) {
		ERRSYS_FATALPRINT("Fail to open Data Exchange Table\n");
		goto err1;
	}
	retval = 0;

    l0032_xtable_close();
err1:
    return retval;
}

int parse_arguments(int argc, char* argv[], struct t0022_0st *t22)
{
	int opt;

	while ((opt = getopt(argc, argv, T0022_0_OPTIONS)) != -1) {
		switch (opt) {
			case 'h':
				usage();
				break;
			case 'o':
				sharedmemory_open();
				exit(0);
				break;
        	case 'w':
				shm_write(atoi(optarg));
				exit(0);
				break;
			case 'r':
				shm_read();
				exit(0);
				break;
			case 'l':
				shm_load();
				exit(0);
				break;
			case 'v':
			default:
				t0022_0_version(argv[0]);
				break;
		}
	}

    return 0;
}

int main(int argc, char* argv[]) {
    int retval = -1;
    struct t0022_0st *t22 = malloc(sizeof(struct t0022_0st));
    if (t22 == NULL) {
        goto err1;
    }
	memset(t22, 0, sizeof(struct t0022_0st));
#ifndef __x86_64__
	errsys_features(ERRSYS_FEATURE_PRINT, ERRSYS_LEVEL_DEBUG, NULL);
	errsys_features(ERRSYS_FEATURE_SYSLOG, ERRSYS_LEVEL_INFO, NULL);

	if (errsys_initialize() < 0) {
		goto err2;
	}
#endif
	t22->appname = argv[0];	
    /* 注册Linux信号处理函数 */
	if (signal_initialize(t22) < 0) {
		ERRSYS_FATALPRINT("Fail to register signal handler\n");
		goto err1;
	}
	parse_arguments(argc, argv, t22);

	ERRSYS_FATALPRINT("T0022-0 Started\n");
	dxtviewer_run(t22);
	retval = 0;
err2:
	ERRSYS_FATALPRINT("dxtviewer_run after\n");
	free(t22);
err1:
	closelog();
	return retval;
}
